package com.gitee.fastmybatis.core.ext;

import com.gitee.fastmybatis.core.FastmybatisConfig;
import org.apache.ibatis.exceptions.ExceptionFactory;
import org.apache.ibatis.executor.ErrorContext;
import org.apache.ibatis.mapping.Environment;
import org.apache.ibatis.session.Configuration;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;

import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;

/**
 * 扩展SqlSessionFactoryBuilder
 *
 * @author thc
 */
public class SqlSessionFactoryBuilderExt extends SqlSessionFactoryBuilder {

    private final String basePackage;

    private final FastmybatisConfig config;

    private final String dialect;
    private final Environment environment;


    public SqlSessionFactoryBuilderExt(String basePackage, FastmybatisConfig config) {
        this(basePackage, config, null, null);
    }

    public SqlSessionFactoryBuilderExt(String basePackage, FastmybatisConfig config, String dialect, Environment environment) {
        this.basePackage = basePackage;
        this.config = config;
        this.dialect = dialect;
        this.environment = environment;
    }


    public SqlSessionFactoryBuilderContext buildSqlSessionFactoryBuilderContext(InputStream inputStream, String environment, Properties properties) {
        try {
            XMLConfigBuilderExt parser = new XMLConfigBuilderExt(
                    inputStream,
                    environment,
                    properties,
                    this.basePackage,
                    this.config,
                    this.dialect
            );
            Configuration configuration = parser.parse();
            return buildSqlSessionFactoryBuilderContext(parser.getMapperLocationsBuilder(), configuration);
        } catch (Exception e) {
            throw ExceptionFactory.wrapException("Error building SqlSession.", e);
        } finally {
            ErrorContext.instance().reset();
            try {
                inputStream.close();
            } catch (IOException e) {
                // Intentionally ignore. Prefer previous error.
            }
        }
    }

    public SqlSessionFactoryBuilderContext buildSqlSessionFactoryBuilderContext(MapperLocationsBuilder mapperLocationsBuilder, Configuration configuration) {
        if (configuration.getEnvironment() == null) {
            configuration.setEnvironment(this.environment);
        }
        return new SqlSessionFactoryBuilderContext(mapperLocationsBuilder, this, configuration);
    }



}
